
#include "StdAfx.h"
#include "NetInstanceBuilder.h"
#include "NetLibs.h"
#include "NetService.h"
#include "IOCP_IOListener.h"
#include "SELECT_IOListener.h"
#include "EPoll_IOListener.h"

#ifdef WIN32

NetInstanceBuilderWindows::NetInstanceBuilderWindows(){
}

NetInstanceBuilderWindows::~NetInstanceBuilderWindows(){
}

Network_IOListener* NetInstanceBuilderWindows::createListener( std::string force_poller, size_t server_port ){
	bool advanced_poller = false;	
	Network_IOListener* listener = 0;
	NetworkConfig* config = NetService::Instance()->getNetworkConfig();

	if( force_poller != "none" ){
		if( force_poller == "iocp" ){
			listener = new IOCP_IOListener();
			config->poller_type( DEF_POLLER_IOCP );
			return listener;
		}
		else if( force_poller == "select" ){
			listener = new SELECT_IOListener();
			config->poller_type( DEF_POLLER_SELECT );
			return listener;
		}		

		return 0;
	}

	advanced_poller = IOCP_IOListener::availableThisListener();

	if( advanced_poller && server_port ){
		listener = new IOCP_IOListener();
		config->poller_type( DEF_POLLER_IOCP );
	}
	else{
		listener = new SELECT_IOListener();
		config->poller_type( DEF_POLLER_SELECT );
	}

	return listener;
}

NetworkSession* NetInstanceBuilderWindows::createSession( size_t server_port ){
	BlanketLock lock( &lock_ );	

	NetworkSession* session = 0;	
	
	if( server_port == 0 ){	
		session = instance_sync_.alloc();
	}	
	else{
		NetworkConfig* conf = NetService::Instance()->getNetworkConfig();

		if( conf->poller_type() == DEF_POLLER_SELECT )
			session = instance_sync_.alloc();
		else
			session = instance_ovl_.alloc();
	}	
	
	return session;
}

//#include <DebugAddressCompare.h>
//extern DebugAddressCompare<int> g_comp;
void NetInstanceBuilderWindows::deleteSession( NetworkSession* session, size_t server_port ){
	LOG_DEBUG( LOG_SERVICE( "instance" )->Log("%s - %u - %u", __FUNCTION__, __LINE__, session) );
	
	BlanketLock lock( &lock_ );

	if(! server_port ){		
		if(! instance_sync_.free( (SessionSync*)session ) ){
			LOG_ERR( LOG_SERVICE( "instance" )->Log("err release = %s - %u", __FUNCTION__, __LINE__) );
		}
	}
	else{
		NetworkConfig* conf = NetService::Instance()->getNetworkConfig();

		if( conf->poller_type() == DEF_POLLER_SELECT ){
			if(! instance_sync_.free( (SessionSync*)session ) ){
				LOG_ERR( LOG_SERVICE( "instance" )->Log("err release = %s - %u", __FUNCTION__, __LINE__) );
			}
		}
		else{
			((SessionOverlapped*)session)->shutdown();

			if(! instance_ovl_.free( (SessionOverlapped*)session ) ){
				LOG_ERR( LOG_SERVICE( "instance" )->Log("err release = %s - %u", __FUNCTION__, __LINE__) );
			}
		}	
	}
}

#endif

#ifdef LINUX

NetInstanceBuilderLinux::NetInstanceBuilderLinux(){
}

NetInstanceBuilderLinux::~NetInstanceBuilderLinux(){
}

Network_IOListener* NetInstanceBuilderLinux::createListener( std::string force_poller, size_t server_port ){
	bool advanced_poller = false;	
	Network_IOListener* listener = 0;
	NetworkConfig* config = NetService::Instance()->getNetworkConfig();

	if( force_poller != "none" ){
		if( force_poller == "epoll" ){
			listener = new EPoll_IOListener();
			config->poller_type( DEF_POLLER_EPOLL );
			
			return listener;
		}
		else if( force_poller == "select" ){
			listener = new SELECT_IOListener();
			config->poller_type( DEF_POLLER_SELECT );

			return listener;
		}		

		return 0;
	}

	advanced_poller = EPoll_IOListener::availableThisListener();

	if( advanced_poller && server_port ){
		listener = new EPoll_IOListener();
		config->poller_type( DEF_POLLER_EPOLL );
	}
	else{
		listener = new SELECT_IOListener();
		config->poller_type( DEF_POLLER_SELECT );
	}

	return listener;
}

NetworkSession* NetInstanceBuilderLinux::createSession( size_t server_port ){
	BlanketLock lock( &lock_ );
	NetworkSession* session = instance_sync_.alloc();
	
	return session;
}

void NetInstanceBuilderLinux::deleteSession( NetworkSession* session, size_t server_port ){
	LOG_DEBUG( LOG_SERVICE( "instance" )->Log("%s - %u - %u", __FUNCTION__, __LINE__, session) );

	BlanketLock lock( &lock_ );
	((SessionSync*)session)->shutdown();	
	instance_sync_.free( (SessionSync*)session );
}

#endif

#ifdef OSX

NetInstanceBuilderOsX::NetInstanceBuilderOsX(){
}

NetInstanceBuilderOsX::~NetInstanceBuilderOsX(){
}

Network_IOListener* NetInstanceBuilderOsX::createListener( std::string force_poller, size_t server_port ){
	bool advanced_poller = false;	
	Network_IOListener* listener = 0;
	NetworkConfig* config = NetService::Instance()->getNetworkConfig();

	if( force_poller != "none" ){
		if( force_poller == "select" ){
			listener = new SELECT_IOListener();
			config->SetPollerType( DEF_POLLER_SELECT );

			return listener;
		}		

		return 0;
	}	

	listener = new SELECT_IOListener();
	config->SetPollerType( DEF_POLLER_SELECT );	

	return listener;
}

NetworkSession* NetInstanceBuilderOsX::createSession( size_t server_port ){
	BlanketLock lock( &lock_ );
	NetworkSession* session = instance_sync_.alloc();
	
	return session;
}

void NetInstanceBuilderOsX::deleteSession( NetworkSession* session, size_t server_port ){
	LOG_DEBUG( LOG_SERVICE( "instance" )->Log("%s - %u - %u", __FUNCTION__, __LINE__, session) );

	BlanketLock lock( &lock_ );
	((SessionSync*)session)->shutdown();	
	instance_sync_.free( (SessionSync*)session );
}

#endif
